#include "composite_configuration_provider.h"
#include "json_file_provider.h"
#include <QRegularExpression>
#include <algorithm>
#include <QJsonDocument>
#include <QJsonObject>
#include <QJsonArray>
#include <QFile>
#include <QDir>

namespace infrastructure {

// ========== ConfigurationSection 实现 ==========

ConfigurationSection::ConfigurationSection(const QString& path, const QHash<QString, QVariant>& data, 
                                           std::shared_ptr<CompositeConfigurationProvider> provider)
    : m_path(path), m_data(data), m_provider(provider) {
}

QString ConfigurationSection::getString(const QString& key, const QString& defaultValue) const {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->getString(fullKey, defaultValue);
    }
    return m_data.value(key, defaultValue).toString();
}

int ConfigurationSection::getInt(const QString& key, int defaultValue) const {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->getInt(fullKey, defaultValue);
    }
    return m_data.value(key, defaultValue).toInt();
}

bool ConfigurationSection::getBool(const QString& key, bool defaultValue) const {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->getBool(fullKey, defaultValue);
    }
    return m_data.value(key, defaultValue).toBool();
}

double ConfigurationSection::getDouble(const QString& key, double defaultValue) const {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->getDouble(fullKey, defaultValue);
    }
    return m_data.value(key, defaultValue).toDouble();
}

bool ConfigurationSection::setString(const QString& key, const QString& value) {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->setString(fullKey, value);
    }
    return false;
}

bool ConfigurationSection::setInt(const QString& key, int value) {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->setInt(fullKey, value);
    }
    return false;
}

bool ConfigurationSection::setBool(const QString& key, bool value) {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->setBool(fullKey, value);
    }
    return false;
}

bool ConfigurationSection::setDouble(const QString& key, double value) {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->setDouble(fullKey, value);
    }
    return false;
}

bool ConfigurationSection::removeKey(const QString& key) {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->removeKey(fullKey);
    }
    return false;
}

bool ConfigurationSection::save() {
    if (auto provider = m_provider.lock()) {
        return provider->save();
    }
    return false;
}

kernel::SubscriptionHandle ConfigurationSection::subscribe(const QString& key, kernel::ConfigurationChangeCallback callback) {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->subscribe(fullKey, callback);
    }
    return 0;
}

void ConfigurationSection::unsubscribe(kernel::SubscriptionHandle handle) {
    if (auto provider = m_provider.lock()) {
        provider->unsubscribe(handle);
    }
}

bool ConfigurationSection::isValid() const {
    if (auto provider = m_provider.lock()) {
        return provider->isValid();
    }
    return true;
}

infrastructure::ValidationResult ConfigurationSection::getValidationResult() const {
    if (auto provider = m_provider.lock()) {
        return provider->getValidationResult();
    }
    // 如果provider不可用，返回一个有效的验证结果
    return infrastructure::ValidationResult(true);
}

std::optional<std::shared_ptr<kernel::IConfigurationSection>> ConfigurationSection::getSection(const QString& key) const {
    QString fullKey = buildKey(key);
    if (auto provider = m_provider.lock()) {
        return provider->getSection(fullKey);
    }
    return std::nullopt;
}

QString ConfigurationSection::getPath() const {
    return m_path;
}

std::optional<QString> ConfigurationSection::getValue() const {
    if (m_data.contains("")) {
        return m_data.value("").toString();
    }
    return std::nullopt;
}

// 配置导入导出方法实现
bool ConfigurationSection::exportToFile(const QString& filePath) const {
    // ConfigurationSection不支持直接导出到文件，委托给父级provider
    if (auto provider = m_provider.lock()) {
        return provider->exportToFile(filePath);
    }
    return false;
}

bool ConfigurationSection::importFromFile(const QString& filePath) {
    // ConfigurationSection不支持直接从文件导入，委托给父级provider
    if (auto provider = m_provider.lock()) {
        return provider->importFromFile(filePath);
    }
    return false;
}

QString ConfigurationSection::exportToJson() const {
    // ConfigurationSection不支持直接导出JSON，委托给父级provider
    if (auto provider = m_provider.lock()) {
        return provider->exportToJson();
    }
    return "{}";
}

bool ConfigurationSection::importFromJson(const QString& jsonString) {
    // ConfigurationSection不支持直接导入JSON，委托给父级provider
    if (auto provider = m_provider.lock()) {
        return provider->importFromJson(jsonString);
    }
    return false;
}

QString ConfigurationSection::buildKey(const QString& key) const {
    if (m_path.isEmpty()) {
        return key;
    }
    if (key.isEmpty()) {
        return m_path;
    }
    return m_path + ":" + key;
}

// ========== CompositeConfigurationProvider 实现 ==========

CompositeConfigurationProvider::CompositeConfigurationProvider()
    : m_nextHandle(1), m_validationResult(true) {
}

CompositeConfigurationProvider::~CompositeConfigurationProvider() {
    // 停止所有提供者的监视
    for (auto& provider : m_providers) {
        provider->stopWatching();
    }
}

QString CompositeConfigurationProvider::getString(const QString& key, const QString& defaultValue) const {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    return m_mergedData.value(normalizedKey, defaultValue).toString();
}

int CompositeConfigurationProvider::getInt(const QString& key, int defaultValue) const {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    return m_mergedData.value(normalizedKey, defaultValue).toInt();
}

bool CompositeConfigurationProvider::getBool(const QString& key, bool defaultValue) const {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    return m_mergedData.value(normalizedKey, defaultValue).toBool();
}

double CompositeConfigurationProvider::getDouble(const QString& key, double defaultValue) const {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    return m_mergedData.value(normalizedKey, defaultValue).toDouble();
}

kernel::SubscriptionHandle CompositeConfigurationProvider::subscribe(const QString& key, kernel::ConfigurationChangeCallback callback) {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    
    Subscription subscription;
    subscription.handle = m_nextHandle++;
    subscription.key = normalizedKey;
    subscription.callback = callback;
    
    m_subscriptions.append(subscription);
    return subscription.handle;
}

void CompositeConfigurationProvider::unsubscribe(kernel::SubscriptionHandle handle) {
    QMutexLocker locker(&m_mutex);
    
    auto it = std::find_if(m_subscriptions.begin(), m_subscriptions.end(),
                          [handle](const Subscription& sub) { return sub.handle == handle; });
    
    if (it != m_subscriptions.end()) {
        m_subscriptions.erase(it);
    }
}

bool CompositeConfigurationProvider::isValid() const {
    QMutexLocker locker(&m_mutex);
    return m_validationResult.isValid;
}

infrastructure::ValidationResult CompositeConfigurationProvider::getValidationResult() const {
    QMutexLocker locker(&m_mutex);
    return m_validationResult;
}

std::optional<std::shared_ptr<kernel::IConfigurationSection>> CompositeConfigurationProvider::getSection(const QString& key) const {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    
    QHash<QString, QVariant> subData = getSubData(normalizedKey);
    if (subData.isEmpty()) {
        return std::nullopt;
    }
    
    auto section = std::make_shared<ConfigurationSection>(normalizedKey, subData, 
                                                         std::const_pointer_cast<CompositeConfigurationProvider>(shared_from_this()));
    return section;
}

void CompositeConfigurationProvider::addProvider(std::shared_ptr<IConfigurationProvider> provider) {
    if (!provider) {
        qWarning() << "尝试添加空的配置提供者";
        return;
    }
    
    QMutexLocker locker(&m_mutex);
    
    // 检查是否已经存在相同的提供者
    auto it = std::find_if(m_providers.begin(), m_providers.end(),
                          [provider](const std::shared_ptr<IConfigurationProvider>& p) {
                              return p.get() == provider.get();
                          });
    
    if (it != m_providers.end()) {
        qWarning() << "配置提供者已经存在，跳过添加";
        return;
    }
    
    m_providers.append(provider);
    
    // 按优先级排序
    std::sort(m_providers.begin(), m_providers.end(),
              [](const std::shared_ptr<IConfigurationProvider>& a, 
                 const std::shared_ptr<IConfigurationProvider>& b) {
                  return a->getPriority() > b->getPriority();
              });
    
    // 重新合并数据
    mergeData();
    validateConfiguration();
    setupProviderCallbacks();
    
}

void CompositeConfigurationProvider::removeProvider(std::shared_ptr<IConfigurationProvider> provider) {
    if (!provider) {
        return;
    }
    
    QMutexLocker locker(&m_mutex);
    
    auto it = std::find_if(m_providers.begin(), m_providers.end(),
                          [provider](const std::shared_ptr<IConfigurationProvider>& p) {
                              return p.get() == provider.get();
                          });
    
    if (it != m_providers.end()) {
        provider->stopWatching();
        m_providers.erase(it);
        
        // 重新合并数据
        mergeData();
        validateConfiguration();
        
    }
}

void CompositeConfigurationProvider::addValidator(std::shared_ptr<IConfigurationValidator> validator) {
    if (!validator) {
        qWarning() << "尝试添加空的配置验证器";
        return;
    }
    
    QMutexLocker locker(&m_mutex);
    m_validators.append(validator);
    validateConfiguration();
    
}

void CompositeConfigurationProvider::reload() {
    QMutexLocker locker(&m_mutex);
    
    // 重新加载所有提供者的数据
    for (auto& provider : m_providers) {
        try {
            ConfigurationData data = provider->load();
        } catch (const std::exception& e) {
            qWarning() << "重新加载配置提供者失败:" << provider->getDescription() << "错误:" << e.what();
        }
    }
    
    // 重新合并数据
    mergeData();
    validateConfiguration();
    
}

QVector<QString> CompositeConfigurationProvider::getAllKeys() const {
    QMutexLocker locker(&m_mutex);
    return m_mergedData.keys().toVector();
}

QVariant CompositeConfigurationProvider::getValue(const QString& key) const {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    return m_mergedData.value(normalizedKey);
}

// ========== 配置导入导出方法实现 ==========

bool CompositeConfigurationProvider::exportToFile(const QString& filePath) const {
    try {
        QMutexLocker locker(&m_mutex);
        
        QJsonObject configObject;
        
        // 将合并后的配置数据转换为JSON对象
        for (auto it = m_mergedData.begin(); it != m_mergedData.end(); ++it) {
            QString key = it.key();
            QVariant value = it.value();
            
            // 将键按层级分割并构建JSON结构
            QStringList keyParts = key.split(':');
            QJsonObject currentObj = configObject;
            
            for (int i = 0; i < keyParts.size() - 1; ++i) {
                QString part = keyParts[i];
                if (!currentObj.contains(part)) {
                    currentObj[part] = QJsonObject();
                }
                currentObj = currentObj[part].toObject();
            }
            
            // 设置最终的值
            QString finalKey = keyParts.last();
            if (value.type() == QVariant::Bool) {
                currentObj[finalKey] = value.toBool();
            } else if (value.type() == QVariant::Int) {
                currentObj[finalKey] = value.toInt();
            } else if (value.type() == QVariant::Double) {
                currentObj[finalKey] = value.toDouble();
            } else {
                currentObj[finalKey] = value.toString();
            }
            
            // 将修改后的对象重新赋值回configObject
            QJsonObject tempObj = configObject;
            for (int i = 0; i < keyParts.size() - 1; ++i) {
                QString part = keyParts[i];
                if (i == keyParts.size() - 2) {
                    tempObj[part] = currentObj;
                } else {
                    tempObj = tempObj[part].toObject();
                }
            }
            configObject = tempObj;
        }
        
        // 写入文件
        QFile file(filePath);
        if (!file.open(QIODevice::WriteOnly)) {
            qWarning() << "Cannot open file for writing:" << filePath;
            return false;
        }
        
        QJsonDocument doc(configObject);
        file.write(doc.toJson());
        file.close();
        
        return true;
        
    } catch (const std::exception& e) {
        qWarning() << "导出配置失败:" << e.what();
        return false;
    }
}

bool CompositeConfigurationProvider::importFromFile(const QString& filePath) {
    try {
        QFile file(filePath);
        if (!file.open(QIODevice::ReadOnly)) {
            qWarning() << "Cannot open file for reading:" << filePath;
            return false;
        }
        
        QJsonDocument doc = QJsonDocument::fromJson(file.readAll());
        if (doc.isNull()) {
            qWarning() << "无效的JSON格式:" << filePath;
            return false;
        }
        
        QMutexLocker locker(&m_mutex);
        
        // 解析JSON并更新配置数据
        QJsonObject configObject = doc.object();
        QHash<QString, QVariant> newData;
        
        parseJsonObject(configObject, "", newData);
        
        // 更新合并数据
        m_mergedData = newData;
        
        // 重新验证配置
        validateConfiguration();
        
        // 通知订阅者配置已更新
        for (auto it = m_mergedData.begin(); it != m_mergedData.end(); ++it) {
            notifySubscribers(it.key(), it.value());
        }
        
        return true;
        
    } catch (const std::exception& e) {
        qWarning() << "导入配置失败:" << e.what();
        return false;
    }
}

QString CompositeConfigurationProvider::exportToJson() const {
    try {
        QMutexLocker locker(&m_mutex);
        
        QJsonObject configObject;
        
        // 将合并后的配置数据转换为JSON对象
        for (auto it = m_mergedData.begin(); it != m_mergedData.end(); ++it) {
            QString key = it.key();
            QVariant value = it.value();
            
            // 将键按层级分割并构建JSON结构
            QStringList keyParts = key.split(':');
            QJsonObject currentObj = configObject;
            
            for (int i = 0; i < keyParts.size() - 1; ++i) {
                QString part = keyParts[i];
                if (!currentObj.contains(part)) {
                    currentObj[part] = QJsonObject();
                }
                currentObj = currentObj[part].toObject();
            }
            
            // 设置最终的值
            QString finalKey = keyParts.last();
            if (value.type() == QVariant::Bool) {
                currentObj[finalKey] = value.toBool();
            } else if (value.type() == QVariant::Int) {
                currentObj[finalKey] = value.toInt();
            } else if (value.type() == QVariant::Double) {
                currentObj[finalKey] = value.toDouble();
            } else {
                currentObj[finalKey] = value.toString();
            }
            
            // 将修改后的对象重新赋值回configObject
            QJsonObject tempObj = configObject;
            for (int i = 0; i < keyParts.size() - 1; ++i) {
                QString part = keyParts[i];
                if (i == keyParts.size() - 2) {
                    tempObj[part] = currentObj;
                } else {
                    tempObj = tempObj[part].toObject();
                }
            }
            configObject = tempObj;
        }
        
        QJsonDocument doc(configObject);
        return doc.toJson();
        
    } catch (const std::exception& e) {
        qWarning() << "导出JSON配置失败:" << e.what();
        return "{}";
    }
}

bool CompositeConfigurationProvider::importFromJson(const QString& jsonString) {
    try {
        QJsonDocument doc = QJsonDocument::fromJson(jsonString.toUtf8());
        if (doc.isNull()) {
            qWarning() << "无效的JSON格式";
            return false;
        }
        
        QMutexLocker locker(&m_mutex);
        
        // 解析JSON并更新配置数据
        QJsonObject configObject = doc.object();
        QHash<QString, QVariant> newData;
        
        parseJsonObject(configObject, "", newData);
        
        // 更新合并数据
        m_mergedData = newData;
        
        // 重新验证配置
        validateConfiguration();
        
        // 通知订阅者配置已更新
        for (auto it = m_mergedData.begin(); it != m_mergedData.end(); ++it) {
            notifySubscribers(it.key(), it.value());
        }
        
        return true;
        
    } catch (const std::exception& e) {
        qWarning() << "导入JSON配置失败:" << e.what();
        return false;
    }
}

// ========== 私有辅助方法 ==========

void CompositeConfigurationProvider::mergeData() {
    // 这个方法应该在已锁定的上下文中调用
    m_mergedData.clear();
    
    for (auto& provider : m_providers) {
        if (!provider->isAvailable()) {
            continue;
        }
        
        try {
            ConfigurationData data = provider->load();
            for (auto it = data.values.begin(); it != data.values.end(); ++it) {
                QString key = normalizeKey(it.key());
                QVariant value = it.value();
                
                // 高优先级的提供者会覆盖低优先级的值
                m_mergedData[key] = value;
            }
        } catch (const std::exception& e) {
            qWarning() << "加载配置提供者失败:" << provider->getDescription() << "错误:" << e.what();
        }
    }
}

void CompositeConfigurationProvider::validateConfiguration() {
    // 这个方法应该在已锁定的上下文中调用
    m_validationResult = ValidationResult(true);
    
    for (auto& validator : m_validators) {
        ValidationResult result = validator->validate(m_mergedData);
        
        // 合并验证结果
        for (const auto& error : result.errors) {
            m_validationResult.errors.append(error);
            if (error.severity == "error") {
                m_validationResult.isValid = false;
            }
        }
    }
}

void CompositeConfigurationProvider::notifySubscribers(const QString& key, const QVariant& newValue) {
    // 这个方法应该在已锁定的上下文中调用
    QString normalizedKey = normalizeKey(key);
    
    for (const auto& subscription : m_subscriptions) {
        if (subscription.key == normalizedKey || subscription.key == "*") {
            try {
                subscription.callback(normalizedKey, newValue.toString());
            } catch (const std::exception& e) {
                qWarning() << "配置变更回调执行失败:" << e.what();
            }
        }
    }
}

void CompositeConfigurationProvider::onProviderChange(const QString& key, const QVariant& newValue) {
    QMutexLocker locker(&m_mutex);
    QString normalizedKey = normalizeKey(key);
    QVariant oldValue = m_mergedData.value(normalizedKey);
    
    // 重新合并数据
    mergeData();
    validateConfiguration();
    
    // 通知订阅者
    QVariant currentValue = m_mergedData.value(normalizedKey);
    if (currentValue != oldValue) {
        notifySubscribers(normalizedKey, currentValue);
    }
}

void CompositeConfigurationProvider::setupProviderCallbacks() {
    // 这个方法应该在已锁定的上下文中调用
    for (auto& provider : m_providers) {
        provider->setChangeCallback([this](const QString& key, const QVariant& newValue) {
            onProviderChange(key, newValue);
        });
        provider->startWatching();
    }
}

QHash<QString, QVariant> CompositeConfigurationProvider::getSubData(const QString& prefix) const {
    // 这个方法应该在已锁定的上下文中调用
    QHash<QString, QVariant> result;
    QString searchPrefix = prefix.isEmpty() ? "" : prefix + ":";
    
    for (auto iter = m_mergedData.begin(); iter != m_mergedData.end(); ++iter) {
        const QString& key = iter.key();
        if (key.startsWith(searchPrefix)) {
            QString subKey = key.mid(searchPrefix.length());
            result[subKey] = iter.value();
        }
    }
    
    return result;
}

bool CompositeConfigurationProvider::keyExists(const QString& key) const {
    // 这个方法应该在已锁定的上下文中调用
    QString normalizedKey = normalizeKey(key);
    return m_mergedData.contains(normalizedKey);
}

QString CompositeConfigurationProvider::normalizeKey(const QString& key) const {
    // 标准化键名：移除多余的冒号，转换为小写
    QString normalized = key.trimmed();
    
    // 移除连续的冒号
    normalized.replace(QRegularExpression(":+"), ":");
    
    // 移除开头和结尾的冒号
    if (normalized.startsWith(":")) {
        normalized = normalized.mid(1);
    }
    if (normalized.endsWith(":")) {
        normalized.chop(1);
    }
    
    return normalized;
}

void CompositeConfigurationProvider::parseJsonObject(const QJsonObject& obj, const QString& prefix, QHash<QString, QVariant>& result) {
    for (auto it = obj.begin(); it != obj.end(); ++it) {
        QString key = it.key();
        QJsonValue value = it.value();
        
        QString fullKey = prefix.isEmpty() ? key : prefix + ":" + key;
        
        if (value.isObject()) {
            // 递归处理嵌套对象
            parseJsonObject(value.toObject(), fullKey, result);
        } else if (value.isArray()) {
            // 处理数组
            QJsonArray array = value.toArray();
            QStringList stringArray;
            for (const QJsonValue& arrayValue : array) {
                stringArray.append(arrayValue.toString());
            }
            result[fullKey] = stringArray.join(",");
        } else {
            // 处理基本类型
            if (value.isBool()) {
                result[fullKey] = value.toBool();
            } else if (value.isDouble()) {
                result[fullKey] = value.toDouble();
            } else {
                result[fullKey] = value.toString();
            }
        }
    }
}

// === 写入方法实现 ===

bool CompositeConfigurationProvider::setString(const QString& key, const QString& value) {
    return setValue(key, QVariant(value));
}

bool CompositeConfigurationProvider::setInt(const QString& key, int value) {
    return setValue(key, QVariant(value));
}

bool CompositeConfigurationProvider::setBool(const QString& key, bool value) {
    return setValue(key, QVariant(value));
}

bool CompositeConfigurationProvider::setDouble(const QString& key, double value) {
    return setValue(key, QVariant(value));
}

bool CompositeConfigurationProvider::removeKey(const QString& key) {
    QMutexLocker locker(&m_mutex);
    
    // 尝试从支持写入的提供者中删除
    for (auto& provider : m_providers) {
        if (auto jsonProvider = std::dynamic_pointer_cast<JsonFileProvider>(provider)) {
            if (jsonProvider->removeValue(key)) {
                // 重新加载数据以更新缓存
                mergeData();
                
                // 通知订阅者
                notifySubscribers(key, QVariant());
                return true;
            }
        }
    }
    
    return false;
}

bool CompositeConfigurationProvider::save() {
    QMutexLocker locker(&m_mutex);
    
    
    // 打印开机自检相关的数据
    
    // 尝试保存到所有支持写入的提供者
    bool success = false;
    int jsonProviderCount = 0;
    for (auto& provider : m_providers) {
        if (auto jsonProvider = std::dynamic_pointer_cast<JsonFileProvider>(provider)) {
            jsonProviderCount++;
            ConfigurationData data;
            data.values = m_mergedData;
            if (jsonProvider->saveData(data)) {
                success = true;
            } else {
            }
        }
    }
    
    
    return success;
}

bool CompositeConfigurationProvider::setValue(const QString& key, const QVariant& value) {
    QMutexLocker locker(&m_mutex);
    
    
    // 尝试写入到第一个支持写入的提供者（通常是JsonFileProvider）
    for (auto& provider : m_providers) {
        if (auto jsonProvider = std::dynamic_pointer_cast<JsonFileProvider>(provider)) {
            if (jsonProvider->updateValue(key, value)) {
                // 更新内存缓存
                m_mergedData[key] = value;
                
                // 通知订阅者
                notifySubscribers(key, value);
                return true;
            } else {
            }
        }
    }
    
    return false;
}

} // namespace infrastructure 